//===============================================================================
// Microsoft patterns & practices Enterprise Library Contribution
// Query Application Block
//===============================================================================

using System;
using Microsoft.Practices.EnterpriseLibrary.Configuration.Design;

namespace EntLibContrib.Query.Configuration.Design
{
	/// <summary>
	/// This class builds the configuration data from the node hierarchy
	/// to save data from the console to configuration.
	/// </summary>
	public class QuerySettingsBuilder
	{
		#region Fields
		private QuerySettingsNode querySettingsNode;
		private IConfigurationUIHierarchy hierarchy;
		private QuerySettings queryConfiguration;
		#endregion

		#region Construction
		/// <summary>
		/// Initializes a new instance of the <see cref="QuerySettingsBuilder"/> class.
		/// </summary>
		/// <param name="serviceProvider">The service provider.</param>
		/// <param name="querySettingsNode">The query settings node.</param>
		public QuerySettingsBuilder (IServiceProvider serviceProvider, QuerySettingsNode querySettingsNode)
		{
			this.querySettingsNode = querySettingsNode;
			hierarchy = ServiceHelper.GetCurrentHierarchy(serviceProvider);
			queryConfiguration = new QuerySettings();
		}
		#endregion

		#region Public Methods
		/// <summary>
		/// Builds the configuration data for the query settings.
		/// </summary>
		/// <returns>A query settings instance</returns>
		public QuerySettings Build ()
		{
			if (!querySettingsNode.RequirePermission)	// don't set if false
				queryConfiguration.SectionInformation.RequirePermission = querySettingsNode.RequirePermission;

			BuildCommands();
			BuildParameterSets();
			BuildQueries();

			return queryConfiguration;
		}
		#endregion

		#region Private Methods
		private void BuildCommands()
		{
			CommandCollectionNode commandCollectionNode = (CommandCollectionNode)hierarchy.FindNodeByType(typeof(CommandCollectionNode));
			foreach (CommandNode commandNode in commandCollectionNode.Nodes)
			{
				queryConfiguration.Commands.Add(commandNode.CommandData);
			}
		}

		private void BuildParameterSets()
		{
			ParameterCollectionNode parameterCollectionNode = (ParameterCollectionNode)hierarchy.FindNodeByType(typeof(ParameterCollectionNode));
			foreach (ParameterSetNode parameterSetNode in parameterCollectionNode.Nodes)
			{
				queryConfiguration.ParameterSets.Add(BuildParameters(parameterSetNode));
			}
		}

		private static ParameterSetData BuildParameters(ParameterSetNode parameterSetNode)
		{
			ParameterSetData parameterSetData = parameterSetNode.ParameterSetData;
			foreach (ParameterNode parameterNode in parameterSetNode.Nodes)
			{
				parameterSetData.Parameters.Add(parameterNode.ParameterData);
			}

			return parameterSetData;
		}

		private void BuildQueries()
		{
			QueryCollectionNode queryCollectionNode = (QueryCollectionNode)hierarchy.FindNodeByType(typeof(QueryCollectionNode));
			foreach (QueryBaseNode queryNode in queryCollectionNode.Nodes)
			{
				queryConfiguration.Queries.Add(queryNode.QueryData);
			}
		}
		#endregion
	}
}